Skip to content

test(tokens): add UnspentTokensIteratorBy prepared-statement comparison benchmark#1855

Open
sid200727 wants to merge 1 commit into
LFDT-Panurus:mainfrom
sid200727:test/prepared-statements-benchmark
Open

test(tokens): add UnspentTokensIteratorBy prepared-statement comparison benchmark#1855
sid200727 wants to merge 1 commit into
LFDT-Panurus:mainfrom
sid200727:test/prepared-statements-benchmark

Conversation

@sid200727

Copy link
Copy Markdown
Contributor

Summary

Adds a benchmark comparing UnspentTokensIteratorBy executed via the current dynamic query-building path against the same query executed via a statement prepared once and reused, to get concrete numbers for the discussion in #1183.

Changes

-> Extracted the query-building logic from UnspentTokensIteratorBy into a standalone buildUnspentTokensIteratorByQuery function (pure refactor, no behavior change — verified via existing TestTokens suite, all 28 subtests pass including ListUnspentTokensByWallets)
-> Added RunUnspentTokensIteratorByPreparedComparison benchmark comparing:

  • UnspentTokensIteratorBy_Dynamic: current production path (query built + executed fresh each call)
  • UnspentTokensIteratorBy_Prepared: same query, prepared once via readDB.PrepareContext, reused via stmt.QueryContext
    -> Wired into the existing Postgres benchmark suite as BenchmarkTokenStorePreparedComparison

Results (median of 3 runs, same seed as existing baseline: 1000 tokens, wallet0/GOLD, 4 workers, 5s window)

Metric Dynamic (current) Prepared Delta
Throughput 3,334 ops/s 3,879 ops/s +11% (range +6.5% to +17% across runs)
P99 latency ~8.3ms ~2.1ms -73% (consistent across all runs)
Allocs/op 131-132 27 -80% (deterministic, zero variance)

Testing

Verified with -count=3, all runs consistent. Existing TestTokens suite passes unchanged, confirming the query-building extraction preserves behavior.

Notes for the Reviewer

Related to #1183. This PR is the measurement step only, no production behavior changes. Happy to proceed with the actual prepared-statement implementation (pre-prepare fixed variants + fallback to dynamic building, per the design discussed on the issue) if these numbers make the case.

@AkramBitar

Copy link
Copy Markdown
Contributor

Hello @sid200727 ,
Thanks a lot for your effort and work on that PR.
This looks promising

See my comment in #1183 (comment)

If the query is dynamic, then I am wondering how do we determine which parameter combinations are actually common enough to justify pre-prepared statements? Wouldn’t identifying these combinations require runtime tracking/analysis, and could that add additional overhead or complexity?

Regards,
Akram

@AkramBitar AkramBitar self-requested a review July 6, 2026 11:37
@AkramBitar AkramBitar added this to the Q3/26 milestone Jul 6, 2026
…on benchmark

Extracts the query-building logic from UnspentTokensIteratorBy into a
standalone buildUnspentTokensIteratorByQuery function (pure refactor, no
behavior change), and adds a new benchmark comparing:

- UnspentTokensIteratorBy_Dynamic: the current production path, which
  builds and executes the query fresh on every call.
- UnspentTokensIteratorBy_Prepared: the same query, prepared once via
  readDB.PrepareContext and reused across calls via stmt.QueryContext.

Same seed and worker config as the existing baseline (1000 tokens,
wallet0/GOLD, 4 workers, 5s window) so results are directly comparable.

Median of 3 runs against Postgres:
- Throughput: 3,334 -> 3,879 ops/s (+11%, range +6.5% to +17%)
- P99 latency: ~8.3ms -> ~2.1ms (-73%, consistent across all runs)
- Allocs/op: 131-132 -> 27 (-80%, deterministic across all runs)

See discussion on LFDT-Panurus#1183.

Signed-off-by: Siddhi Khandelwal <siddhi.200727@gmail.com>
@sid200727 sid200727 force-pushed the test/prepared-statements-benchmark branch from a96dd50 to 3c9d830 Compare July 6, 2026 15:45
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants